﻿package common.proxy;

import java.lang.reflect.Method;

import util.DebugUtil;

import common.service.IService;
import common.transaction.ITransactionController;
import common.transaction.TransactionAnnotation;
import common.transaction.TransactionControllerFactory;
import common.transaction.TransactionAnnotation.TransactionType;


/**
 * 
 * 服务类的代理类
 *
 */
public class ServiceProxy extends ObjectProxy {

	public ServiceProxy(Object realObj) {
		super(realObj);
	}

	@Override
	public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
		DebugUtil.print("调用" + this.realObj.getClass().getName() + "的方法" + method.getName());
		if(proxy instanceof IService) {
			TransactionAnnotation an = method.getAnnotation(TransactionAnnotation.class);
			if(an == null) {
				return method.invoke(this.realObj, args);
			} else {
				if(an.transactionType().equals(TransactionType.QUERY)) {//查询不用启动事务
					return this.query((IService)proxy, method, args);
				} else {//保存数据需要启动事务
					return this.save((IService)proxy, method, args);
				}
			}
		} else {
			throw new Exception(proxy.getClass().getName() + "需要实现接口" + IService.class.getName());
		}
	}
	
	//查询
	private Object query(IService serviceProxy, Method method, Object[] args) throws Throwable {
		ITransactionController transController = TransactionControllerFactory
		.getInstance().createTransactionController(serviceProxy, TransactionControllerFactory.TransactionType_Connection);

		Object ret = null;
		try {
			ret = method.invoke(this.realObj, args);
		} catch (Exception e) {
			e.printStackTrace();
			throw new Exception(e);
		} finally {
			transController.end();// 关闭连接
		}
		return ret;
	}
	
	//保存
	private Object save(IService serviceProxy, Method method, Object[] args) throws Throwable {
		ITransactionController transController = TransactionControllerFactory
		.getInstance().createTransactionController(serviceProxy, TransactionControllerFactory.TransactionType_Connection);
		
		Object trans = null;
		Object ret = null;
		try {
			trans = transController.begin(); // 事务开始
			
			ret = method.invoke(this.realObj, args);
			
			transController.commit(trans);// 事务提交
		} catch (Exception e) {
			e.printStackTrace();
			transController.rollback(trans);// 事务回滚
			throw new Exception(e);
		} finally {
			transController.end();// 关闭连接
		}
		return ret;
	}

}
